package fcnet

import (
	"sync"

	"gitee.com/fcsvr/fc/fclog"
)

type ConnMgr struct {
	ConnMap map[int]*Conn
	lock    sync.RWMutex
}

func NewConnMgr() *ConnMgr {
	c := &ConnMgr{
		ConnMap: make(map[int]*Conn),
	}
	return c
}

func (this *ConnMgr) AddConn(conn *Conn) {
	this.lock.Lock()
	defer this.lock.Unlock()

	this.ConnMap[conn.GetConnID()] = conn
}

func (this *ConnMgr) DelConn(id int) {
	this.lock.Lock()
	defer this.lock.Unlock()

	delete(this.ConnMap, id)
}

func (this *ConnMgr) GetConn(id int) *Conn {
	this.lock.Lock()
	defer this.lock.Unlock()

	conn, ok := this.ConnMap[id]
	if !ok {
		fclog.Error("ConnMgr GetConn no connid = %d", id)
		return nil
	}
	return conn
}

func (this *ConnMgr) Len() int {
	return len(this.ConnMap)
}

func (this *ConnMgr) ClearAllConn() {
	//this.lock.Lock()
	//defer this.lock.Unlock()

	fclog.Debug("ConnMgr Clear All Conn")
	for id, conn := range this.ConnMap {
		conn.Stop()
		delete(this.ConnMap, id)
	}
	fclog.Info("ConnMgr ClearAllConn")
}

func (this *ConnMgr) PushMsg(msgid uint32, msgbody []byte, connids ...int) error {
	msg := NewMsg(msgid, msgbody)
	data, err := msg.DoPack()
	if err != nil {
		fclog.Error("ConnMgr PushMsg id = %d DoPack err = %v", msgid, err)
		return err
	}
	for _, connid := range connids {
		conn := this.GetConn(connid)
		if conn == nil {
			continue
		}
		conn.SendDataToChan(data)
	}
	return nil
}
